package rr.sb.getContent.parsers;

import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.nio.charset.Charset;
import java.util.LinkedHashSet;
import java.util.Set;

import rr.sb.getContent.Config;
import rr.sb.getContent.Content;

public abstract class ContentParser {

    BufferedWriter out;
    StringBuilder content = new StringBuilder();
    String contentTitle;
    String contentCategory;
    int count = 0;
    Set<Content> contentSet = new LinkedHashSet<Content>();
    Set<String> contentTitleSet = new LinkedHashSet<String>();
    Set<String> contentCategorySet = new LinkedHashSet<String>();
    Config config;

    public void parse(Config config) throws IOException {
	this.config = config;
	File source = new File(config.getSourceDir());
	if (source.exists()) {
	    doParse(source);
	    writeContentToDestinationFile();
	    log("DONE !");
	} else {
	    log("Source dir " + config.getSourceDir() + " does not exists.");
	}
    }

    public void doParse(File source) {
	File[] files = source.listFiles();
	for (File file : files) {
	    if (file.isFile()) {
		if (file.getName().endsWith(".html") || file.getName().endsWith(".htm")) {
		    try {
			parseFile(file);
		    } catch (IOException e) {
			log("Error parsing file " + file.getAbsolutePath());
			e.printStackTrace();
		    }
		} else {
		    log("Skip file " + file.getAbsolutePath());

		}

	    } else {
		doParse(file);
	    }
	}
    }

    public void parseFile(File file) throws IOException {

	log("Parsing file " + file.getAbsolutePath());

	BufferedReader br = new BufferedReader(new InputStreamReader(new FileInputStream(file), Charset.forName("UTF-8")));

	String line;

	while ((line = br.readLine()) != null) {

	    String currentLine = line.trim();

	    processLine(currentLine);
	}
	br.close();
    }

    public abstract void processLine(String currentLine);

    void writeContentToDestinationFile() throws IOException {
	File f = new File(config.getDestinationDir());
	if (!f.exists()) {
	    f.mkdirs();
	}

	f = new File(config.getDestinationDir() + "\\result.txt");
	if (!f.exists()) {
	    f.createNewFile();
	}

	out = new BufferedWriter(new OutputStreamWriter(new FileOutputStream(f), Charset.forName("UTF-8")));

	for (Content content : contentSet) {
	    out.write(content.toString() + "\r\n\r\n");
	}
	log(contentCategorySet.size() + " categories.");
	log(contentTitleSet.size() + " titles.");
	log(contentSet.size() + " contents.");
	out.close();

    }

    void addContent() {
	Content newContent = new Content(replaceChars(contentTitle), replaceChars(content.toString()), replaceChars(contentCategory));
	contentSet.add(newContent);
	contentTitleSet.add(newContent.getTitle());
	contentCategorySet.add(newContent.getCategory());
	log(++count + "");
	//log(newContent.getContent());

	contentTitle = null;
	contentCategory = null;
	content = new StringBuilder();
    }

    void addContentLine(String line) {
	//log(line);
	content.append(line);
    }

    public String replaceChars(String s) {
	return cleanHtml(s.replace("<br />", "\r\n").replace("&#8220;", "\"").replace("&#8221;", "\"").replace("&#8211;", "-")
		.replace("&#8230;", "...").replace("&#8216;", "'").replace("&#8217;", "'").replace("&#8243;", "\""));
    }

    public String cleanHtml(String s) {
	if (s.contains("<")) {
	    String retVal = "";
	    retVal += s.substring(0, s.indexOf("<"));
	    retVal += s.substring(s.indexOf(">") + 1, s.indexOf("</"));
	    retVal += s.substring(s.indexOf(">", s.indexOf("</")) + 1);
	    return cleanHtml(retVal);
	} else {
	    return s;
	}
    }

    public void log(String s) {
	System.out.println(s);
    }
}
